/*******************************************************************************
 * Copyright (c) 2010 European Software Institute - Tecnalia.
 * All rights reserved. This program and the accompanying materials
 * are made available under the terms of the Eclipse Public License v1.0
 * which accompanies this distribution, and is available at
 * http://www.eclipse.org/legal/epl-v10.html
 *
 * Contributors:
 *     Author - Adri�n Noguero (adrian.noguero@esi.es)
 *     
 *******************************************************************************/
package es.esi.gemde.vv.modelanalyzer.service.impl;

import java.util.HashMap;
import java.util.Vector;

import es.esi.gemde.vv.modelanalyzer.exceptions.NoSuchToolException;
import es.esi.gemde.vv.modelanalyzer.service.IAnalysisTool;
import es.esi.gemde.vv.modelanalyzer.service.IToolOperation;

/**
 * A class that manages the tools registered in the Model Analysis Service.
 *
 * @author Adri�n Noguero (adrian.noguero@esi.es)
 * @version 1.0
 * @since 1.0
 *
 */
public class ToolRegistry {

	private HashMap<String,IAnalysisTool> registry;
	//private Vector<IMethodologyAdapter> adapters;
	
	/**
	 * Constructor of the class
	 *
	 */
	public ToolRegistry() {
		registry = new HashMap<String,IAnalysisTool>();
		//adapters = new Vector<IMethodologyAdapter>();
	}
	
	/**
	 * Returns an array with the names of all the tools available in the repository.
	 * 
	 * @return the name array.
	 */
	public String [] getToolNames() {
		return registry.keySet().toArray(new String[0]);
	}
	
	/**
	 * Returns an array with all the tool implementations available in the repository.
	 * 
	 * @return the tool array.
	 */
	public IAnalysisTool [] getTools() {
		return registry.values().toArray(new IAnalysisTool[0]);
	}
	
	/**
	 * This method returns the tool implementation in the repository given its name or null if the tool is not available.
	 * 
	 * @param name the name of the tool to be returned.
	 * @return the implementation of the tool with the given name or null.
	 */
	public IAnalysisTool getToolByName(String name) {
		return registry.get(name);
	}
	
	/**
	 * This method registers a tool in the repository.
	 * 
	 * @param name the name of the tool to be registered.
	 * @param tool the implementation of the tool.
	 * @throws IllegalArgumentException if the provided name is null or invalid, or if the provided implementation is null.
	 */
	public void addTool(String name, IAnalysisTool tool) throws IllegalArgumentException {
		if (name == null || name.equals("") || registry.containsKey(name)) {
			throw new IllegalArgumentException("The provided tool name is not valid");
		}
		
		if (tool == null) {
			throw new IllegalArgumentException("A null tool implementation was provided");
		}
		
		registry.put(name, tool);
	}
	
	/**
	 * This method returns all the categories for which at least one tool is registered.
	 * 
	 * @return an array of String, containing the names of the available tool categories, or null if no categories are defined.
	 */
	public String [] getToolCategories() {
		Vector<String> categories = new Vector<String>();
		for (IAnalysisTool tool : registry.values()) {
			if (!categories.contains(tool.getCategory())) {
				categories.add(tool.getCategory());
			}
		}
		if (categories.size() != 0) {
			return categories.toArray(new String[0]);
		}
		else {
			return null;
		}
	}

	
	/**
	 * This method returns an array containing the operations available for a given tool.
	 * 
	 * @param toolName the name of the tool.
	 * @return an array containing the IToolOperation implementations.
	 * @throws NoSuchToolException if the name of the tool can't be located in the registry.
	 */
	public IToolOperation[] getToolOperations(String toolName) throws NoSuchToolException {
		IAnalysisTool tool = registry.get(toolName);
		if (tool == null) {
			throw new NoSuchToolException("The provided tool name is not registered in GEMDE.");
		}
		else {
			return tool.getOperations();
		}
	}
	
	/*public void addAdapter (IMethodologyAdapter adapter) {
		if (adapter != null && adapter.getTool() != null && adapter.getMethod() != null) {
			adapters.add(adapter);
		}
	}*/
	
}
